package com.gebro.classifier;

import java.util.ArrayList;
import java.util.Collections;
import java.util.List;
import java.util.Map;



/**
 * 
 * 
 * 
 * @author hadi.elmougy
 *
 */
public class EuclideanDistance {

	private Point point;
	private Matrix matrix;
	private List<Node> distanceList;

	
	


	/**
	 * 
	 * 
	 * @param matrix
	 * @param point
	 */
	public EuclideanDistance(Matrix matrix, Point point) {
		this.matrix = matrix;
		this.point = point;
	}

	
	/**
	 * 
	 * 
	 */
	private void calculateDistance(){
		Matrix diffMat = Matrix.tile(this.matrix, point);
		Matrix dm = diffMat.subtract(matrix);
		Matrix sqDiffMat = dm.power(2);
		List<Node> sqDistances = sumAxis1(sqDiffMat);
		Collections.sort(sqDistances);
		this.distanceList = sqDistances;
	}

	
	/**
	 * 
	 * 
	 * 
	 * @param matrix
	 * @return
	 */
	private List<Node> sumAxis1(Matrix matrix) {
		List<Node> m = new ArrayList<Node>();
		List<MatrixElement> els = matrix.getElements();
		for(MatrixElement el : els){
			m.add(new Node(el, Math.pow(el.getX()+el.getY(),0.5)));
		}
		return m;
	}

	
	/**
	 * 
	 * 
	 * @return
	 */
	public MatrixElement getNearestPoint() {
		calculateDistance();
		Node node= null;
		try{
			node = this.distanceList.get(0);
		}catch(IndexOutOfBoundsException e){
			throw new IndexOutOfBoundsException();
		}
		return node.getEl();
	}
	
	
	/**
	 * 
	 * 
	 * 
	 * @return
	 */
	public List<Node> getSortedDistanceList() {
		return distanceList;
	}

}
